/*
 * 版权所有 (C) 2015 知启蒙(ZHIQIM) 保留所有权利。[遇见知启蒙，邂逅框架梦]
 * 
 * https://zhiqim.org/project/zhiqim_components/zhiqim_manager.htm
 *
 * Zhiqim Manager is licensed under Mulan PSL v2.
 * You can use this software according to the terms and conditions of the Mulan PSL v2.
 * You may obtain a copy of Mulan PSL v2 at:
 *          http://license.coscl.org.cn/MulanPSL2
 * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
 * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
 * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
 * See the Mulan PSL v2 for more details.
 */
package org.zhiqim.manager.dao;

import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

import org.zhiqim.httpd.HttpRequest;
import org.zhiqim.kernel.annotation.AnAlias;
import org.zhiqim.kernel.model.tree.Tree;
import org.zhiqim.kernel.model.tree.TreeBuilder;
import org.zhiqim.kernel.util.Arrays;
import org.zhiqim.kernel.util.Asserts;
import org.zhiqim.kernel.util.Validates;
import org.zhiqim.manager.dbo.ZmrDept;
import org.zhiqim.manager.dbo.ZmrOperator;
import org.zhiqim.orm.ORM;
import org.zhiqim.orm.ORMException;
import org.zhiqim.orm.dbo.Selector;
import org.zhiqim.orm.dbo.Updater;

/**
 * 部门数据访问对象
 *
 * @version v1.0.0 @author zouzhigang 2017-8-23 新建与整理
 */
@AnAlias("ZmrDeptDao")
public class ZmrDeptDao
{
    /**
     * 获取部门列表，根据部门级别、部门排序数、部门ID排序
     * 
     * @return              部门列表
     * @throws ORMException ORM异常
     * @throws SQLException SQL异常
     */
    public static List<ZmrDept> list() throws ORMException, SQLException
    {
        return ORM.table().list(ZmrDept.class, new Selector().addOrderbyAsc("deptLevel,deptSeq,deptId"));
    }
    
    /**
     * 获取部门树，根据部门级别、部门排序数、部门ID排序
     * 
     * @return              部门列表
     * @throws ORMException ORM异常
     * @throws SQLException SQL异常
     */
    public static Tree<ZmrDept> tree() throws ORMException, SQLException
    {
        return TreeBuilder.newTree(list(), "parentId", "deptId");
    }
    
    /**
     * 通过部门编号读取部门名称
     * 
     * @param deptId        部门编号
     * @return              部门名称
     * @throws ORMException ORM异常
     * @throws SQLException SQL异常
     */
    public static String name(long deptId) throws ORMException, SQLException
    { 
        ZmrDept item = ORM.table().item(ZmrDept.class, deptId);
        return (item == null)?null:item.getDeptName();
    }
    
    /**
     * 是否是部门经理
     * 
     * @param request       请求对象
     * @param operatorCode  部门经理编码
     * @return              =true表示是
     * @throws ORMException ORM异常
     * @throws SQLException SQL异常
     */
    public static boolean isDeptManager(HttpRequest request, String operatorCode) throws ORMException, SQLException
    {
        return !ORM.table().list(ZmrDept.class, new Selector("deptId", "deptManager", operatorCode)).isEmpty();
    }
    
    /**
     * 获取部门经理下属操作员账号列表
     * 
     * @param operatorCode  部门经理编码
     * @param recursion     是否向在递归
     * @return              下属操作员列表
     * @throws Exception    异常
     */
    public static List<String> getDeptOperatorCodeList(String operatorCode, boolean recursion) throws Exception
    {
        Asserts.assertNotEmpty(operatorCode, "操作员账号不允许为空");
        
        List<ZmrDept> deptList = ORM.table().list(ZmrDept.class, new Selector("deptManager", operatorCode));
        if (deptList.isEmpty())
            return new ArrayList<>();
            
        List<String> list = new ArrayList<>();
        List<ZmrOperator> operatorList = ORM.table().list(ZmrOperator.class);
        opr:for (ZmrOperator operator : operatorList)
        {
            String deptAll = recursion?operator.getOperatorDeptAll():operator.getOperatorDept();
            for (ZmrDept dept : deptList)
            {
                if (Validates.isContain(deptAll, ",", dept.getDeptId()))
                {
                    list.add(operator.getOperatorCode());
                    continue opr;
                }
            }
        }
        
        return list;
    }
    
    /**
     * 获取部门经理下属操作员列表
     * 
     * @param operatorCode  部门经理编码
     * @param recursion     是否向在递归
     * @return              下属操作员列表
     * @throws Exception    异常
     */
    public static List<ZmrOperator> getDeptOperatorList(String operatorCode, boolean recursion) throws Exception
    {
        Asserts.assertNotEmpty(operatorCode, "操作员账号不允许为空");
        
        List<ZmrDept> deptList = ORM.table().list(ZmrDept.class, new Selector("deptManager", operatorCode));
        if (deptList.isEmpty())
            return new ArrayList<>();
            
        List<ZmrOperator> list = new ArrayList<>();
        List<ZmrOperator> operatorList = ORM.table().list(ZmrOperator.class);
        opr:for (ZmrOperator operator : operatorList)
        {
            String deptAll = recursion?operator.getOperatorDeptAll():operator.getOperatorDept();
            for (ZmrDept dept : deptList)
            {
                if (Validates.isContain(deptAll, ",", dept.getDeptId()))
                {
                    list.add(operator);
                    continue opr;
                }
            }
        }
        
        return list;
    }
    
    /**
     * 更新部门负责人所属部门
     * @param request           请求对象
     * @param operatorCodeList  操作员账号列表
     * @param deptId            部门编码
     * @param deptParentAll     部门所有父节点
     * @throws Exception
     */
    public static void doUpdateDeptManeger(HttpRequest request, List<String> operatorCodeList, String deptId, String deptParentAll) throws Exception
    {
        for (String operatorCode : operatorCodeList)
        {
            ZmrOperator operator = ORM.table().item(ZmrOperator.class, operatorCode);
            if(operator == null)
            {
                request.returnHistory("操作员不存在");
                return;
            }
            
            String operatorDept = operator.getOperatorDept();
            if (Validates.isEmptyBlank(operatorDept))
                operatorDept = deptId;
            else
                operatorDept += "," + deptId;
            
            String operatorDeptAll = operator.getOperatorDeptAll();
            if (Validates.isEmptyBlank(operatorDeptAll))
                operatorDeptAll = deptParentAll + "," + deptId;
            else
                operatorDeptAll += "," + deptParentAll + "," + deptId;
            
            //去重
            operatorDept = Arrays.toFilterSameStr(Arrays.toStringArray(operatorDept));
            operatorDeptAll = Arrays.toFilterSameStr(Arrays.toStringArray(operatorDeptAll));
            
            Updater updater = new Updater();
            updater.addMust("operatorCode", operatorCode);
            updater.addField("operatorDept", operatorDept);
            updater.addField("operatorDeptAll",operatorDeptAll);
            ORM.table().update(ZmrOperator.class, updater);
        }
    }
}
